import { isEmpty } from '@/utils'
import { CartGroupType, ActItemType, CartItemType } from '@/pages/ShoppingCart/typing';
import { createSlice, current } from '@reduxjs/toolkit'


interface SelectedCartItem {
    cartId: string | number;
    quantity: number;
    skuId: string | number;
    skuPrice: string | number;
}

type ExtShopItemListType = Record<string, CartGroupType & {
    shopId: string | number;
    actIds: Array<string | number>;
}>;

type ExtActItemListType = Record<string, ActItemType & {
    actId: string | number;
    cartIds: Array<string | number>;
    shopId: string | number;
}>;

type ExtCartItemListType = Record<string, CartItemType & {
    cartId: string | number;
    actId: string | number;
    shopId: string | number;
}>;

interface CartStateType {
    initData: boolean;
    cartList: CartGroupType[];
    shopItemIndex: ExtShopItemListType,
    actItemIndex: ExtActItemListType,
    cartItemIndex: ExtCartItemListType,
    maxCartNum: number,
    selectedCart: Record<string, SelectedCartItem>,
    selectedCartNum: number,
    selectedCartIds: string[],
    sumInfo: {
        totalAmount: 0,
        discountAmount: 0,
        totalCartNum: 0,
        selectedCartNum: 0,
        selectedCartIds: string[]
    }
};



const genActId = (shopId: string | number, actId: string | number) => {
    return `${shopId}_${actId}`;
};

const buildIndex = (cartList: CartGroupType[]) => {
    const shopIndex = {} as ExtShopItemListType;
    const actIndex = {} as ExtActItemListType;
    const cartIndex = {} as ExtCartItemListType;

    cartList?.forEach((shop) => {
        if (!shop) {
            return;
        }
        const shopId = shop.shopId;
        const actIds = [] as any[];

        shop.actItems?.forEach((actItem) => {
            if (!actItem) {
                return;
            }
            const actId = actItem.actId;
            actIds.push(actId);

            const cartIds = [] as any[];
            actItem.carts?.forEach((cartItem) => {
                if (!cartItem) {
                    return;
                }
                const cartId = cartItem.cartId;
                cartIds.push(cartId);

                cartIndex[`${cartId}`] = {
                    ...cartItem,
                    actId,
                    shopId,
                    cartId
                };
            });

            const actIndexKey = genActId(shopId, actId);
            actIndex[actIndexKey] = {
                ...actItem,
                carts: [],
                cartIds,
                shopId
            };
        })

        shopIndex[`${shopId}`] = {
            ...shop,
            actItems: [],
            actIds,
        };
    });
    return {
        shopIndex,
        actIndex,
        cartIndex
    };
};
/**
 * 查找店铺级别的购物车项
 * 
 * @param cartIndex 
 * @param shopId 
 */
const findShopItem = (shopItemList: ExtShopItemListType, shopId: string | number) => {
    if (isEmpty(shopItemList)) {
        return;
    }
    if (isEmpty(shopId)) {
        return;
    }
    return shopItemList[`${shopId}`];
};

/**
* 查找具体的购物车项
* 
* @param cartList 购物车数组
* @param cartIndex 购物车索引
* @param shopId 
*/
const findCartItem = (cartItemList: ExtCartItemListType, cartId: string | number) => {
    if (isEmpty(cartItemList)) {
        return;
    }
    if (isEmpty(cartId)) {
        return;
    }
    return cartItemList[`${cartId}`];
};

export const findActItem = (actItemList: ExtActItemListType, key: {
    shopId: string | number, actId: string | number
}) => {
    if (isEmpty(actItemList)) {
        return;
    }
    if (isEmpty(key)) {
        return;
    }
    const { shopId, actId } = key;
    const actIdKey = genActId(shopId, actId);
    return actItemList[actIdKey];
}

/***
 * 选中/取消选中购物车项的通用逻辑
 */
const toggleCartSelection = (
    state: CartStateType,
    cartItem: CartItemType,
    isSelected: boolean
) => {
    if (isEmpty(cartItem) || isEmpty(cartItem.cartId)) return;

    const { cartId, quantity, mainSku } = cartItem;

    if (isSelected) {
        state.selectedCart[cartId] = {
            cartId,
            quantity: quantity || 1,
            skuId: mainSku?.skuId || '',
            skuPrice: mainSku?.skuPrice || 0
        };
    } else {
        delete state.selectedCart[cartId];
    }

    // 更新选中ID列表
    state.selectedCartIds = Object.keys(state.selectedCart);
    state.selectedCartNum = state.selectedCartIds.length;
};

/**
 * 删除购物车项的通用逻辑
 */
const removeCartItem = (state: CartStateType, cartId: string | number) => {
    const cartItem = findCartItem(state.cartItemIndex, cartId);
    if (!cartItem) return;

    // 从购物车索引中删除
    delete state.cartItemIndex[`${cartId}`];

    // 从活动中删除引用
    const actItem = findActItem(state.actItemIndex, {
        shopId: cartItem.shopId,
        actId: cartItem.actId
    });

    if (actItem) {
        actItem.cartIds = actItem.cartIds.filter(id => id !== cartId);
    }
    // 从选中列表中移除
    toggleCartSelection(state, cartItem, false);
};

const cartReducerSlice = createSlice({
    name: 'shoppingCart',
    initialState: {
        initData: false,
        cartList: [],
        shopItemIndex: {},
        actItemIndex: {},
        cartItemIndex: {},
        maxCartNum: 50,
        selectedCart: {},
        selectedCartNum: 0,
        selectedCartIds: [],
        sumInfo: {
            totalAmount: 0,
            discountAmount: 0,
            totalCartNum: 0,
            selectedCartNum: 0,
            selectedCartIds: []
        }
    } as CartStateType,
    reducers: {
        updateCartList(state, action) {
            state.cartList = action.payload;

            const { shopIndex, actIndex, cartIndex } = buildIndex(state.cartList);
            state.shopItemIndex = shopIndex;
            state.actItemIndex = actIndex;
            state.cartItemIndex = cartIndex;

            state.initData = true;
        },
        checkAll(state, action) {
            const { checkType } = action.payload;

            Object.keys(state.shopItemIndex)?.forEach(key => {
                const shopItem = state.shopItemIndex?.[key];
                shopItem.checkType = checkType;
            })

            // 更新所有活动
            Object.values(state.actItemIndex).forEach(actItem => {
                if (actItem) {
                    actItem.checkType = checkType;

                    // 更新活动下所有商品
                    actItem.cartIds?.forEach(cartId => {
                        const cartItem = findCartItem(state.cartItemIndex, cartId);
                        if (cartItem) {
                            cartItem.checkType = checkType;
                            toggleCartSelection(state, cartItem, checkType);
                        }
                    });
                }
            });

        },
        checkShopAll(state, action) {
            const { shopId } = action.payload;

            const shopItem = findShopItem(state.shopItemIndex, shopId);
            if (!shopItem) {
                return;
            }
            const newCheckState = !shopItem.checkType;
            shopItem.checkType = newCheckState;

            shopItem.actIds.forEach((actId) => {
                const actItem = findActItem(state.actItemIndex, { shopId, actId });
                if (!actItem) {
                    return;
                }
                // 修改所有活动的选中状态
                if (actItem.checkType !== newCheckState) {
                    actItem.checkType = newCheckState;
                }

                // 修改活动下所有商品的选中状态
                actItem?.cartIds.forEach((cartId) => {
                    const cartItem = findCartItem(state.cartItemIndex, cartId);
                    if (!cartItem) {
                        return;
                    }
                    if (cartItem.checkType !== newCheckState) {
                        cartItem.checkType = newCheckState;
                    }

                    toggleCartSelection(state, cartItem, newCheckState);
                })

            })
        },
        checkItem(state, action) {
            const { cartId, checkType } = action.payload;
            const cartItem = findCartItem(state.cartItemIndex, cartId);
            if (!cartItem) {
                return;
            }
            const newCheckState = !checkType;
            cartItem.checkType = newCheckState;

            const actItem = findActItem(state.actItemIndex, {
                shopId: cartItem.shopId,
                actId: cartItem.actId
            });
            if (actItem) {
                actItem.checkType = actItem.cartIds?.every(item => state.cartItemIndex[item].checkType);
                const shopItem = findShopItem(state.shopItemIndex, actItem.shopId);
                if (shopItem) {
                    shopItem.checkType = shopItem.actIds?.every(item => {
                        const actItem = findActItem(state.actItemIndex, {
                            shopId: shopItem.shopId,
                            actId: item
                        });
                        return actItem?.checkType;
                    });
                }
                toggleCartSelection(state, cartItem, newCheckState);

            }
        },
        deleteSelectedCart(state, action) {
            const selectedCartIds = state.selectedCartIds;
            if (isEmpty(selectedCartIds)) {
                return;
            }
            selectedCartIds?.forEach(cartId => {
                removeCartItem(state, cartId);
            })
        },

        deleteItem(state, action) {
            const { cartId } = action.payload;
            removeCartItem(state, cartId);
        },
        updateQuantity(state, action) {
            const { cartId, quantity } = action.payload;
            if (!cartId) {
                return;
            }
            const cartItem = findCartItem(state.cartItemIndex, cartId);
            if (!cartItem) {
                return;
            }
            cartItem.quantity = quantity;
            if (!cartItem.checkType) {
                cartItem.checkType = true;
            }
            toggleCartSelection(state, cartItem, true);
        }
    }
})

export const {
    updateCartList,
    checkAll,
    checkShopAll,
    checkItem,
    updateQuantity,
    deleteItem,
    deleteSelectedCart

} = cartReducerSlice.actions
export const cartReducerV2 = cartReducerSlice.reducer


